package top.chenfu.blog.service.impl;

import com.alibaba.fastjson.JSON;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import top.chenfu.blog.dao.ArticleMapper;
import top.chenfu.blog.dao.TagsMapper;
import top.chenfu.blog.entity.Article;
import top.chenfu.blog.entity.User;
import top.chenfu.blog.enums.ArticleEnum;
import top.chenfu.blog.service.ArticleService;

import java.sql.Timestamp;
import java.util.Arrays;
import java.util.List;
import java.util.Objects;

/**
 * @Auther chenfu
 * @2019/10/30 17:02
 * @Desc
 */
@Service
@Slf4j
public class ArticleServiceImpl implements ArticleService {

    @Autowired
    private ArticleMapper articleMapper;

    @Autowired
    private TagsMapper tagsMapper;

    @Override
    public List<Article> getArticleByState(int state, Long uid, Integer page, Integer count, String keywords) {
        PageHelper.startPage(page, count);
        List<Article> articles = articleMapper.getArticlesByUseridAndState(uid, keywords, state);
//        log.info("articles === {}", JSON.toJSONString(articles));
        PageInfo<Article> pageInfo = new PageInfo<>(articles);
//        log.info("pageInfo === {}", JSON.toJSONString(pageInfo));
        return pageInfo.getList();
    }

    @Override
    public Integer getArticleCountByState(Integer state, Long id, String keywords) {
        return articleMapper.getArticleCountByState(state, id, keywords);
    }

    @Override
    @Transactional
    public Integer updateArticleState(List<Long> aids, Integer status) {
        if (CollectionUtils.isEmpty(aids) || aids.size() <= 0) {
            return 0;
        }
        int delCount;
        if (ArticleEnum.DIS_ENABLE.getType().equals(status)) {
//            这个就是真删了！
            delCount = (int) aids.stream().filter(id -> articleMapper.deleteByPrimaryKey(id) > 0).count();
        } else {
//            放入回收站
            delCount = (int) aids.stream().filter(id -> {
                Article article = articleMapper.selectByPrimaryKey(id);
                article.setState(ArticleEnum.DIS_ENABLE.getType());
                return articleMapper.updateByPrimaryKeySelective(article) > 0;
            }).count();
        }
        return delCount;
    }

    @Override
    @Transactional
    public Integer restoreArticle(Long articleId) {
        Article article = new Article();
        article.setId(articleId);
        article.setState(ArticleEnum.RESTORE.getType());
        return articleMapper.updateByPrimaryKeySelective(article);
    }

    @Override
    @Transactional
    public Article getArticleById(Long aid) {
        Article article = articleMapper.selectByPrimaryKey(aid);
//        访问次数
        article.setPageView(article.getPageView() + 1);
        articleMapper.updateByPrimaryKeySelective(article);
        return article;
    }

    @Override
    @Transactional
    public Integer addNewArticle(Article article) {
//        处理文章摘要
        if (StringUtils.isBlank(article.getSummary())) {
            String stripHtml = stripHtml(article.getHtmlContent());
            article.setSummary(stripHtml.substring(0, Math.min(stripHtml.length(), 50)));
        }
        if (article.getId() == -1) {
            Timestamp timestamp = new Timestamp(System.currentTimeMillis());
            if (article.getState() == 1) {
                article.setPublishDate(timestamp);
            }
            article.setEditTime(timestamp);
            User principal = (User) SecurityContextHolder.getContext().getAuthentication().getPrincipal();
            article.setUid(principal.getId());
            article.setId(null);
            int insert = articleMapper.insertSelective(article);
//            保存标签数据
            String[] dynamicTags = article.getDynamicTags();
            log.info("标签:{}", JSON.toJSONString(dynamicTags));
            List<String> tagNames = Arrays.asList(dynamicTags);
            if (CollectionUtils.isNotEmpty(tagNames)) {
                return addTagsToArticle(tagNames, article.getId());
            }
            return insert;
        } else {
//            发表文章
            if (article.getState() == 1) {
                article.setPublishDate(new Timestamp(System.currentTimeMillis()));
            }
            article.setEditTime(new Timestamp(System.currentTimeMillis()));
            int i = articleMapper.updateByPrimaryKeySelective(article);
//            保存标签
            List<String> tagNames = Arrays.asList(article.getDynamicTags());
            if (CollectionUtils.isNotEmpty(tagNames)) {
                return addTagsToArticle(tagNames, article.getId());
            }
            return i;
        }

    }

    private Integer addTagsToArticle(List<String> tagNames, Long aid) {
//        删除以前的标签
        tagsMapper.deleteTagsByAid(aid);
//        更新标签库
        tagsMapper.saveTags(tagNames);
//        根据标签查出所有的标签ID
        List<Long> tagIds = tagsMapper.getTagsIdByTagName(tagNames);
//        保存文章和标签的映射关系
        long count = tagIds.stream().map(tagId -> tagsMapper.saveArticleTags(aid, tagId)).count();
        return Math.toIntExact(count == tagNames.size() ? count : -1);
    }

    private String stripHtml(String content) {
        content = content.replaceAll("<p .*?>", "");
        content = content.replaceAll("<br\\s*/?>", "");
        content = content.replaceAll("\\<.*?>", "");
        return content;
    }

}
